<#include "/includes/vars.inc"> 
<#include "/includes/defaults_macro.inc"> 
<@pp.dropOutputFile />
<#list entities.entity as entity>
	<#assign fileName = "${javaDir}${packageDir}/domain/"+entity.@name+".java">
	<#if !pp.outputFileExists(fileName)>
		<@pp.changeOutputFile name="${fileName}" />
    	<#assign name = entity.@name>
package ${project.@rootPackage}.domain;

<#list entity.column.@type as enum>
    <#if enums.enum.@name?seq_contains(enum)>
import ${project.@rootPackage}.domain.enums.${enum};
    </#if>
</#list>
    
<#list entity.column.@type as embed>
    <#if embeddables.embeddable.@name?seq_contains(embed)>
import ${project.@rootPackage}.domain.embed.${embed};
    </#if>
</#list>  

<#include "/includes/fixImportsList.inc">
import java.io.Serializable;
import javax.persistence.Embedded;
import javax.persistence.Enumerated;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.Lob;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
<#if entity["many-to-many"][0]??>
import javax.persistence.ManyToMany;
</#if>
<#if entity["one-to-many"][0]??>
import javax.persistence.OneToMany;
</#if>
<#if entity["many-to-one"][0]??>
import javax.persistence.ManyToOne;
</#if>
<#if entity["one-to-one"][0]??>
import javax.persistence.OneToOne;
</#if>
import javax.persistence.Table;
<#if entity?children.@type?seq_contains("Date")>
import java.util.Date;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;
</#if>


/**
 * Entity class ${entity.@name}
 * <#if project.@author[0]??>@author ${project.@author}</#if>
 */
@Entity
    <#if (entity.@table[0])?? >
@Table(name = "${entity.@table}")
    <#else>
@Table
    </#if>
public class ${name} implements Serializable{
        
    private static final long serialVersionUID = 1L;
    
    <#if config.autoIds??>
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    </#if>

    <#list entity.column as column>    
        <#if column.@primary[0]="true">
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
        <#elseif column.@type = "Date">
    @Column
    @Temporal(TemporalType.DATE)
        <#elseif enums.enum.@name?seq_contains(column.@type)>
    @Enumerated
    	<#elseif embeddables.embeddable.@name?seq_contains(column.@type)>
    @Embedded
        <#elseif column.@type="String" && column.@size[0]??  && (column.@size?number > 256) >
    @Lob
        <#elseif column.@type?cap_first="Boolean">
    @Column(columnDefinition="BOOLEAN")
    	<#else>
    @Column
        </#if>
        <#if column.@required[0]="true">
    //@NotNull    
        </#if>
    private ${column.@type} ${column.@name};
    </#list>

    <#list entity["one-to-one"] as rel>
    <#-- targetEntity=${rel.@entity}.class<#if rel.@fetch[0]??>,fetch=FetchType.${rel.@fetch}</#if> -->
    @OneToOne(targetEntity=${rel.@entity}.class<#if rel.@mappedBy[0]??>,mappedBy="${rel.@mappedBy}"</#if><#if rel.@required[0]="true">,optional=false</#if><#if rel.@fetch[0]="LAZY">,fetch=javax.persistence.FetchType.${rel.@fetch}</#if>)
    private ${rel.@entity} ${rel.@name};
    </#list>   
    <#list entity["one-to-many"] as rel>
    @OneToMany(targetEntity=${rel.@entity}.class<#if rel.@mappedBy[0]??>,mappedBy="${rel.@mappedBy}"</#if><#if rel.@fetch[0]="EAGER">,fetch=javax.persistence.FetchType.${rel.@fetch}</#if>)
    private ${rel.@type}<${rel.@entity}> ${rel.@name};    
    </#list>   
    <#list entity["many-to-one"] as rel>
    @ManyToOne(targetEntity=${rel.@entity}.class<#if rel.@required[0]="true">,optional=false</#if><#if rel.@fetch[0]="LAZY">,fetch=javax.persistence.FetchType.${rel.@fetch}</#if>)
    <#--@ManyToOne(targetEntity=${rel.@entity}.class<#if rel.@fetch[0]??>,fetch=FetchType.${rel.@fetch}</#if><#if rel.@mappedBy[0]??>,mappedBy="${rel.@mappedBy}"</#if><#if rel.@required="true">,optional=false</#if>)-->
    <#--<#if !(rel.@mappedBy[0])??>@JoinColumn(name = "${rel.@entity?upper_case}_ID", referencedColumnName = "id", nullable = true)</#if>  -->  
    private ${rel.@entity} ${rel.@name};
    </#list>   
    <#list entity["many-to-many"] as rel>
    @ManyToMany(targetEntity=${rel.@entity}.class<#if rel.@mappedBy[0]??>,mappedBy="${rel.@mappedBy}"</#if><#if rel.@fetch[0]="EAGER">,fetch=javax.persistence.FetchType.${rel.@fetch}</#if>)
    <#-- <#if !(rel.@mappedBy[0])??>@JoinTable(name = "${rel.@entity?upper_case}_${entity.@name?upper_case}", joinColumns = @JoinColumn(name = "${rel.@entity?upper_case}_ID",referencedColumnName="id"), inverseJoinColumns = @JoinColumn(name = "${entity.@name?upper_case}_ID",referencedColumnName="id"))</#if> -->
    private ${rel.@type}<${rel.@entity}> ${rel.@name};
    </#list>   
    //How to solve fetch eager problem when org.hibernate.loader.MultipleBagFetchException
    //http://blog.eyallupu.com/2010/06/hibernate-exception-simultaneously.html

    /*
    *  Constructors
    */
    public ${name}(){
	<@resolveDefaults entityName="${entity.@name}" /> 
    } 
   

    <#--
    public ${name}(<#list entity.column as column>${column.@type} ${column.@name}<#if column_has_next>,</#if></#list>){
        <#list entity.column as column>
        this.${column.@name}=${column.@name};
        </#list>
    }
    -->

    /*
    *  Methods
    */
    public boolean isPersisted(){
        return id!=null;
    }
    
    @Override
    public boolean equals(Object obj) {
        if (obj == null) {
            return false;
        }
        if (getClass() != obj.getClass()) {
            return false;
        }
        final ${name} other = (${name}) obj;
        if (this.id != other.id && (this.id == null || !this.id.equals(other.id))) {
            return false;
        }
        return true;
    }

    @Override
    public int hashCode() {
        int hash = 0;
        hash += (id != null ? id.hashCode() : 0);
        return hash;
    }

    @Override
    public String toString() {
        StringBuilder sb = new StringBuilder();
        <#if entity.@toString[0]??>
        	<#list entity.@toString?split(",") as col>
        if (${col}!=null && !${col}.toString().isEmpty()){
        	sb.append(${col})<#if col_has_next>.append(" ");<#else>;</#if>
        }
        	</#list>	
        <#else>
        sb.append("${name}:");
        	<#list entity.column as column>    
        sb.append(" ${column.@name}:").append(${column.@name});
        	</#list>
        </#if>
        return sb.toString();
    }
	
    /*
    * HELPERS
    */
 	<#list entity["one-to-many"] as rel>
	<#include "/includes/helperEntity.inc"> 
 	</#list>
 
 	<#list entity["many-to-many"] as rel>
	<#include "/includes/helperEntity.inc"> 
 	</#list>


    /*
    * GETTERS AND SETTERS
    */
    
   <#if config.autoIds??>
    public void setId(Long id){
        this.id=id;
    }    

    public Long getId(){
        return id;
    }
    </#if>
   
    
    <#list entity.column as column>

    public void set${column.@name?cap_first}(${column.@type} ${column.@name}){
        this.${column.@name}=${column.@name};
    }    

    public ${column.@type} get${column.@name?cap_first}(){
        return ${column.@name};
    }
   
        <#if column.@type = "Boolean">
    public ${column.@type} is${column.@name?cap_first}(){
        return ${column.@name};
    }
        </#if>
    </#list>
    <#list entity["one-to-many"] as rel>
    public void set${rel.@name?cap_first}(${rel.@type}<${rel.@entity?cap_first}> ${rel.@name}){
        this.${rel.@name}=${rel.@name};
    }    
      
    public ${rel.@type}<${rel.@entity?cap_first}>  get${rel.@name?cap_first}(){
        return ${rel.@name};
    }
    </#list>
    <#list entity["many-to-many"] as rel>
    public void set${rel.@name?cap_first}(${rel.@type}<${rel.@entity?cap_first}> ${rel.@name}){
        this.${rel.@name}=${rel.@name};
    }    
      
    public ${rel.@type}<${rel.@entity?cap_first}>  get${rel.@name?cap_first}(){
        return ${rel.@name};
    } 

    </#list>
    <#list entity["many-to-one"] as rel>
    public void set${rel.@name?cap_first}(${rel.@entity} ${rel.@name}){
        this.${rel.@name}=${rel.@name};
    }    
      
    public ${rel.@entity} get${rel.@name?cap_first}(){
        return ${rel.@name};
    }

    </#list>
    <#list entity["one-to-one"] as rel>
    public void set${rel.@name?cap_first}(${rel.@entity} ${rel.@name}){
        this.${rel.@name}=${rel.@name};
    }    
      
    public ${rel.@entity} get${rel.@name?cap_first}(){
        return ${rel.@name};
    }

    </#list>
    
    <#--
    <#list embeddables.embeddable as embed>    
    	<#list entity.column as col>
    		<#if col.@type=embed.@name>
   /*
   * Helpers for ${embed.@name}
   */ 	
   				<#list embed.column as column> 
   public void set${column.@name?cap_first}(${column.@type} ${column.@name?uncap_first}){
        this.${col.@name}.set${column.@name?cap_first}(${column.@name?uncap_first});
    } 
    
   				</#list>
        	</#if>
        </#list>
    </#list>
	-->
}
	</#if>
</#list>
